using System;
using System.Collections;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Windows.Forms;

using SPOS.Logic;
using SPOS.UIcomp.Views;

namespace SPOS.UIcomp.Views
{
	public class PropertyCtrl : System.Windows.Forms.UserControl
	{
		private System.Windows.Forms.ListBox listBox = null;		
		protected System.ComponentModel.Container components = null;				

		private CustomPropertyGrid propertyGrid = null;	
		private TextBox editBox = null;
		//imageList for icons...
	
		public PropertyCtrl()
		{			
			InitializeComponent();
			Init();
		}

		//listBox will have fixed width,
		//propertyGrid will take rest of space.
		public void Init()
		{			
			editBox = new TextBox();
			editBox.BorderStyle = BorderStyle.FixedSingle;
			editBox.Dock = DockStyle.Bottom;
			editBox.Hide();	
			
			//hook up the eventhandler to notify inner event outside.			
			listBox.SelectedIndexChanged += new EventHandler(selectedListedItemChangedNotify);

			editBox.KeyPress += new KeyPressEventHandler(textBoxEditOverNotify);
			editBox.LostFocus += new EventHandler(textBoxFocusOverNotify);

			propertyGrid.PropertyValueChanged += new PropertyValueChangedEventHandler(propertyGridChangedNotify);
			propertyGrid.TextChanged += new EventHandler(NotifyPropertyGridChanged);

			listBox.Controls.Add(editBox);	
			
		}

		#region our custom events 
			#region ListBox selectedIndexChanged event handing

			//delegate for our custom event
			public delegate void SelectedItemChanged(object sender, EventArgs e);
			
			//declare this as public event so that it's visible from out side on this control
			public event SelectedItemChanged SelectedItemChangedEvent;

			//notify this event when text changed in the m_txt(textbox) control
			private void selectedListedItemChangedNotify(object sender, EventArgs e)
			{
				if(listBox.SelectedItem != null)
				{	
					propertyGrid.SelectedObject = listBox.SelectedItem;
					SelectedItemChangedEvent(this,e); //handler must be assigned from out side ....
				}
			}
			#endregion

			#region editBox editOver and FocusOver event handing
			public class EditBoxEventArgs: EventArgs
			{
				private string _text; 
				private string _toplevelcontrol;
				public EditBoxEventArgs(string t,string top)	{	this._text = t; this._toplevelcontrol = top;		}
				public string Text		{	get { return _text;	}	}
				public string TopLevelControl { get { return _toplevelcontrol;	}	}
			}

			//delegate for our custom event
			public delegate void TextBoxEditOver(object sender, EditBoxEventArgs e);
				
			//declare this as public event so that it's visible from out side on this control
			public event TextBoxEditOver EditOverEvent;

			//notify this event when text changed in the m_txt(textbox) control
			private void textBoxEditOverNotify(object sender, System.Windows.Forms.KeyPressEventArgs e)
			{
				if ( e.KeyChar == 13 || e.KeyChar == 9 ) //if CR or Horizontal TAB
				{
					if(editBox.Text.Trim() != String.Empty)
					{
						EditBoxEventArgs ee = new EditBoxEventArgs(editBox.Text,this.Name);
						EditOverEvent(sender,ee); //handler must be assigned from out side ....
					}

					editBox.Clear();
					editBox.Hide();		
					editBox.Update(); 

					//select the object we just added.
					if (listBox.Items.Count > 0) listBox.SelectedIndex = listBox.Items.Count - 1;
				}

				if ( e.KeyChar == 27 )  //Escape key was pressed.( restore the changes )
				{
					editBox.Clear();
					editBox.Hide();		
					editBox.Update();  
				}			
			}

			private void textBoxFocusOverNotify(object sender, System.EventArgs e)
			{
				if( editBox.Text.Trim() != String.Empty )
				{
					EditBoxEventArgs ee = new EditBoxEventArgs(editBox.Text,this.Name);
					EditOverEvent(sender,ee); //handler must be assigned from out side ....
				}

				editBox.Hide();			
				editBox.Clear();
			}
			#endregion

			#region PropertyGrid Value changed event handing
			public class PropertyGridChangedEventArgs: EventArgs
			{				
				private string _name;
				public PropertyGridChangedEventArgs(string name)	{ this._name = name;	}
				public string Name { get { return _name;	}	}
			}

			//delegate for our custom event
			public delegate void PropertyGridChanged(object sender, PropertyGridChangedEventArgs e);
				
			//declare this as public event so that it's visible from out side on this control
			public event PropertyGridChanged PropertyValueChangedEvent;

			//notify this event when text changed in the m_txt(textbox) control
			private void propertyGridChangedNotify(object sender,  PropertyValueChangedEventArgs e)
			{
				NotifyPropertyGridChanged(sender,e);
			}
			
			public void NotifyPropertyGridChanged(object sender, EventArgs e)
			{
				PropertyGridChangedEventArgs se = new PropertyGridChangedEventArgs(this.Name);
				PropertyValueChangedEvent(sender,se);				
			}
			#endregion

		#endregion

		protected override void Dispose( bool disposing )
		{
			if( disposing )
			{
				if(components != null)
				{
					components.Dispose();
				}
			}
			base.Dispose( disposing );
		}

		#region Component Designer generated code
		/// <summary> 
		/// Required method for Designer support - do not modify 
		/// the contents of this method with the code editor.
		/// </summary>
		private void InitializeComponent()
		{
			this.propertyGrid = new SPOS.UIcomp.Views.CustomPropertyGrid();
			this.listBox = new System.Windows.Forms.ListBox();
			this.SuspendLayout();
			// 
			// propertyGrid
			// 
			this.propertyGrid.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) 
				| System.Windows.Forms.AnchorStyles.Right)));
			this.propertyGrid.CommandsVisibleIfAvailable = true;
			this.propertyGrid.ExpandOnTab = false;
			this.propertyGrid.LargeButtons = false;
			this.propertyGrid.LineColor = System.Drawing.SystemColors.ScrollBar;
			this.propertyGrid.Location = new System.Drawing.Point(360, 0);
			this.propertyGrid.Name = "propertyGrid";
			this.propertyGrid.PropertySort = System.Windows.Forms.PropertySort.Categorized;
			this.propertyGrid.Size = new System.Drawing.Size(336, 560);
			this.propertyGrid.TabIndex = 0;
			this.propertyGrid.Text = "propertyGrid";
			this.propertyGrid.ViewBackColor = System.Drawing.SystemColors.Window;
			this.propertyGrid.ViewForeColor = System.Drawing.SystemColors.WindowText;
			// 
			// listBox
			// 
			this.listBox.Dock = System.Windows.Forms.DockStyle.Left;
			this.listBox.Location = new System.Drawing.Point(0, 0);
			this.listBox.Name = "listBox";
			this.listBox.Size = new System.Drawing.Size(304, 550);
			this.listBox.TabIndex = 1;
			// 
			// PropertyCtrl
			// 
			this.Controls.Add(this.listBox);
			this.Controls.Add(this.propertyGrid);
			this.Name = "PropertyCtrl";
			this.Size = new System.Drawing.Size(696, 560);
			this.Resize += new System.EventHandler(this.PropertyCtrl_Resize);
			this.ResumeLayout(false);

		}
		#endregion
		
		public void Fill(object[] list)
		{
			listBox.Items.AddRange(list);
		}

		public void Fill(object listItem)
		{
			listBox.Items.Add(listItem);
		}

		public object GetItem()
		{
			return listBox.SelectedItem;	
		}

		public void removeCurrentItem()
		{
			if(listBox.SelectedItem != null)
				listBox.Items.RemoveAt(listBox.SelectedIndex);

			listBox.ClearSelected();
			propertyGrid.SelectedObject = null;
		}

		public int CurrentItem
		{
			get { return (listBox.SelectedItem != null) ? ((ILogicBase) listBox.SelectedItem).id :  -1;	}
		}
		
		public object SelectedObject
		{
			get { return this.propertyGrid.SelectedObject;	}
			set { this.propertyGrid.SelectedObject = value;	}
		}

		public void AddBtnPressed()
		{
			this.listBox.ClearSelected();
			this.propertyGrid.SelectedObject = null;
			editBox.Show();
			editBox.Focus();
		}

		private void PropertyCtrl_Resize(object sender, System.EventArgs e)
		{
			listBox.Size = new Size(this.Width * 2 / 5, this.Height);			
			propertyGrid.Size = new Size(this.Width - listBox.Width - 15, this.Height);
			propertyGrid.Location = new Point(listBox.Width + 15, 0);
		}
	}
}
